package com.scratch.common.service;

import com.alibaba.cloud.commons.lang.StringUtils;
import com.scratch.common.cache.constant.CacheConstants;
import com.scratch.common.core.utils.core.StrUtil;
import com.scratch.common.core.web.enums.ErrorCode;
import com.scratch.common.core.web.result.R;
import com.scratch.common.redis.constant.RedisConstants;
import com.scratch.common.redis.service.RedisService;
import com.scratch.common.service.db.domain.BaseOrderEntity;
import com.scratch.common.service.db.domain.BaseTicketLoadEntity;
import com.scratch.core.api.AuthDto;
import com.scratch.core.api.cp.domain.dto.BaseCpDto;
import com.scratch.core.api.cpAuthPlay.domain.dto.BaseCpAuthPlayDto;
import com.scratch.core.api.org.domain.dto.BaseOrgDto;
import com.scratch.core.api.orgAuthPlay.domain.dto.BaseOrgAuthPlayDto;
import com.scratch.core.api.site.domain.dto.BaseSiteDto;
import com.scratch.core.api.siteAuthPlay.domain.dto.BaseSiteAuthPlayDto;
import com.scratch.core.api.terminal.domain.dto.BaseTerminalDto;
import com.scratch.core.api.terminalModel.domain.dto.BaseTerminalModelDto;
import com.scratch.core.api.ticket.domain.dto.BaseTicketDto;
import com.scratch.core.enums.EnumAuthBus;
import com.scratch.core.enums.EnumAuthPlay;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.support.atomic.RedisAtomicLong;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.stream.Collectors;

@Service
public class CommonService {
    @Autowired
    private RedisService redisService;


    public List<BaseTicketDto> getTicketList(R r) {
        return redisService.getMultiCacheMapValue(CacheConstants.CacheType.TICKET.getCode(), ((AuthDto) r.getData()).getSiteAuthSellPlayList());
    }

    public BaseTicketDto getTicket(String ticketId) {
        return redisService.getCacheMapValue(CacheConstants.CacheType.TICKET.getCode(), ticketId);
    }

    public Map<String, BaseTicketLoadEntity> getTicketLoadMap(String devNo) {
        String baseTicketLoadKey = StrUtil.format(RedisConstants.BaseKey.BASE_TICKET_LOAD.getCode(), devNo);
        return redisService.getCacheMap(baseTicketLoadKey);
    }

    public BaseTerminalModelDto getTerminalModel(String modelId) {
        return redisService.getCacheMapValue(CacheConstants.CacheType.TERMINAL_MODEL.getCode(), modelId);
    }

    public BaseTicketLoadEntity getBaseTicketLoad(String devNo, String hp) {
        String baseTicketLoadKey = StrUtil.format(RedisConstants.BaseKey.BASE_TICKET_LOAD.getCode(), devNo);
        return redisService.getCacheMapValue(baseTicketLoadKey, hp);
    }

    public BaseOrderEntity getBaseOrderEntity(String orderNo) {
        return redisService.getCacheMapValue(RedisConstants.BaseKey.BASE_ORDER.getCode(), orderNo);
    }


    public long getDataVersion(String key) {
        RedisAtomicLong counter = new RedisAtomicLong(key, redisService.redisTemplate.getRequiredConnectionFactory());
        return counter.incrementAndGet();
    }


    /**
     * 获取可售游戏列表
     *
     * @return
     */
    public R sellAuthCheck(String devNo) {
        BaseTerminalDto baseTerminalDto = redisService.getCacheMapValue(CacheConstants.CacheType.TERMINAL.getCode(), devNo);
        if (Objects.isNull(baseTerminalDto)) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_TERMINAL_NOT_FOUND);
        }
        if (Objects.isNull(baseTerminalDto.getSiteId()) || StringUtils.isBlank(baseTerminalDto.getSiteId().toString())) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_TERMINAL_UNAUTHORIZED);
        }
        BaseSiteDto baseSiteDto = redisService.getCacheMapValue(CacheConstants.CacheType.SITE.getCode(), baseTerminalDto.getSiteId().toString());
        if (baseSiteDto.getAuthBus().indexOf(String.valueOf(EnumAuthBus.SELL.getCode())) < 0) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_SITE_UNAUTHORIZED_SELL_OR_CASH_PERMISSION);
        }
        BaseCpDto baseCpDto = redisService.getCacheMapValue(CacheConstants.CacheType.CP.getCode(), baseSiteDto.getCpId().toString());
        if (baseCpDto.getAuthBus().indexOf(String.valueOf(EnumAuthBus.SELL.getCode())) < 0) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_CP_UNAUTHORIZED_SELL_OR_CASH_PERMISSION);
        }
        BaseOrgDto baseOrgDto = redisService.getCacheMapValue(CacheConstants.CacheType.ORG.getCode(), baseCpDto.getAreaId().toString());
        if (baseOrgDto.getAuthBus().indexOf(String.valueOf(EnumAuthBus.SELL.getCode())) < 0) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_ORG_UNAUTHORIZED_SELL_OR_CASH_PERMISSION);
        }

        //网点、渠道、机构授权 一个areaId下只能有一个机构
        Map<String, BaseSiteAuthPlayDto> baseSiteAuthPlayDtoMap = redisService.getCacheMap(StrUtil.format(CacheConstants.CacheType.SITE_AUTH_PLAY.getCode(), baseSiteDto.getId().toString()));
        List<Object> siteAuthSellPlayList = baseSiteAuthPlayDtoMap.entrySet().stream().filter(x -> x.getValue().getAuthSell().equals(String.valueOf(EnumAuthPlay.AUTHORIZED.getCode()))).map(x -> {
            return x.getValue().getBaseTicketId().toString();
        }).collect(Collectors.toList());
        if (siteAuthSellPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_SITE_UNAUTHORIZED_PLAY);
        }

        Map<String, BaseCpAuthPlayDto> baseCpAuthPlayDtoMap = redisService.getCacheMap(StrUtil.format(CacheConstants.CacheType.CP_AUTH_PLAY.getCode(), baseCpDto.getId().toString()));
        List<Object> cpAuthSellPlayList = baseCpAuthPlayDtoMap.entrySet().stream().filter(x -> x.getValue().getAuthSell().equals(String.valueOf(EnumAuthPlay.AUTHORIZED.getCode()))).map(x -> {
            return x.getValue().getBaseTicketId().toString();
        }).collect(Collectors.toList());
        if (cpAuthSellPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_CP_UNAUTHORIZED_PLAY);
        }

        Map<String, BaseOrgAuthPlayDto> baseOrgAuthPlayDtoMap = redisService.getCacheMap(StrUtil.format(CacheConstants.CacheType.ORG_AUTH_PLAY.getCode(), baseOrgDto.getId().toString()));
        List<Object> orgAuthSellPlayList = baseOrgAuthPlayDtoMap.entrySet().stream().filter(x -> x.getValue().getAuthSell().equals(String.valueOf(EnumAuthPlay.AUTHORIZED.getCode()))).map(x -> {
            return x.getValue().getBaseTicketId().toString();
        }).collect(Collectors.toList());
        if (orgAuthSellPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_ORG_UNAUTHORIZED_PLAY);
        }
        //取机构、渠道、网点游戏授权交集
        siteAuthSellPlayList.retainAll(cpAuthSellPlayList);
        siteAuthSellPlayList.retainAll(orgAuthSellPlayList);
        if (siteAuthSellPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_RETAINALL_UNAUTHORIZED_PLAY);
        }
        return R.ok(AuthDto.builder().baseTerminalDto(baseTerminalDto).baseSiteDto(baseSiteDto).baseCpDto(baseCpDto).baseOrgDto(baseOrgDto).siteAuthSellPlayList(siteAuthSellPlayList).build());
    }




    /**
     * 获取可售游戏列表
     *
     * @return
     */
    public R cashAuthCheck(String devNo) {
        BaseTerminalDto baseTerminalDto = redisService.getCacheMapValue(CacheConstants.CacheType.TERMINAL.getCode(), devNo);
        if (Objects.isNull(baseTerminalDto)) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_TERMINAL_NOT_FOUND);
        }
        if (Objects.isNull(baseTerminalDto.getSiteId()) || StringUtils.isBlank(baseTerminalDto.getSiteId().toString())) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_TERMINAL_UNAUTHORIZED);
        }
        BaseSiteDto baseSiteDto = redisService.getCacheMapValue(CacheConstants.CacheType.SITE.getCode(), baseTerminalDto.getSiteId().toString());
        if (baseSiteDto.getAuthBus().indexOf(String.valueOf(EnumAuthBus.CASH.getCode())) < 0) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_SITE_UNAUTHORIZED_SELL_OR_CASH_PERMISSION);
        }
        BaseCpDto baseCpDto = redisService.getCacheMapValue(CacheConstants.CacheType.CP.getCode(), baseSiteDto.getCpId().toString());
        if (baseCpDto.getAuthBus().indexOf(String.valueOf(EnumAuthBus.CASH.getCode())) < 0) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_CP_UNAUTHORIZED_SELL_OR_CASH_PERMISSION);
        }
        BaseOrgDto baseOrgDto = redisService.getCacheMapValue(CacheConstants.CacheType.ORG.getCode(), baseCpDto.getAreaId().toString());
        if (baseOrgDto.getAuthBus().indexOf(String.valueOf(EnumAuthBus.CASH.getCode())) < 0) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_ORG_UNAUTHORIZED_SELL_OR_CASH_PERMISSION);
        }

        //网点、渠道、机构授权 一个areaId下只能有一个机构
        Map<String, BaseSiteAuthPlayDto> baseSiteAuthPlayDtoMap = redisService.getCacheMap(StrUtil.format(CacheConstants.CacheType.SITE_AUTH_PLAY.getCode(), baseSiteDto.getId().toString()));
        List<Object> siteAuthCashPlayList = baseSiteAuthPlayDtoMap.entrySet().stream().filter(x -> x.getValue().getAuthCash().equals(String.valueOf(EnumAuthPlay.AUTHORIZED.getCode()))).map(x -> {
            return x.getValue().getBaseTicketId().toString();
        }).collect(Collectors.toList());
        if (siteAuthCashPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_SITE_UNAUTHORIZED_PLAY);
        }

        Map<String, BaseCpAuthPlayDto> baseCpAuthPlayDtoMap = redisService.getCacheMap(StrUtil.format(CacheConstants.CacheType.CP_AUTH_PLAY.getCode(), baseCpDto.getId().toString()));
        List<Object> cpAuthCashPlayList = baseCpAuthPlayDtoMap.entrySet().stream().filter(x -> x.getValue().getAuthCash().equals(String.valueOf(EnumAuthPlay.AUTHORIZED.getCode()))).map(x -> {
            return x.getValue().getBaseTicketId().toString();
        }).collect(Collectors.toList());
        if (cpAuthCashPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_CP_UNAUTHORIZED_PLAY);
        }

        Map<String, BaseOrgAuthPlayDto> baseOrgAuthPlayDtoMap = redisService.getCacheMap(StrUtil.format(CacheConstants.CacheType.ORG_AUTH_PLAY.getCode(), baseOrgDto.getId().toString()));
        List<Object> orgAuthCashPlayList = baseOrgAuthPlayDtoMap.entrySet().stream().filter(x -> x.getValue().getAuthCash().equals(String.valueOf(EnumAuthPlay.AUTHORIZED.getCode()))).map(x -> {
            return x.getValue().getBaseTicketId().toString();
        }).collect(Collectors.toList());
        if (orgAuthCashPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_ORG_UNAUTHORIZED_PLAY);
        }
        //取机构、渠道、网点游戏授权交集
        siteAuthCashPlayList.retainAll(cpAuthCashPlayList);
        siteAuthCashPlayList.retainAll(orgAuthCashPlayList);
        if (siteAuthCashPlayList.isEmpty()) {
            return R.fail(ErrorCode.TERMINAL_GETPLAYLIST_RETAINALL_UNAUTHORIZED_PLAY);
        }
        return R.ok(AuthDto.builder().baseTerminalDto(baseTerminalDto).baseSiteDto(baseSiteDto).baseCpDto(baseCpDto).baseOrgDto(baseOrgDto).siteAuthSellPlayList(siteAuthCashPlayList).build());
    }

}
